﻿using System.Web;
using System.Text.RegularExpressions;
using System.IO;

namespace  Source.Web.FrameWork
{
    public class DownloadHelper
    {
        #region Fields

        public const string CONTENT_TYPE_DOC = "application/word";
        public const string CONTENT_TYPE_PDF = "application/pdf";
        public const string CONTENT_TYPE_TXT = "text/plain";
        public const string CONTENT_TYPE_OCTETSTREAM = "application/octet-stream";

        private const string FILE_TYPE_DOC = "doc";
        private const string FILE_TYPE_TXT = "txt";
        private const string FILE_TYPE_PDF = "pdf";

        #endregion


        #region Public Methods

        public static void LoadFile(string fileName, string contentType, object documentData)
        {
            var response = HttpContext.Current.Response;

            response.ClearHeaders();
            response.Clear();

            response.ContentType = contentType;
            AddAttachmentHeader(fileName);
            WriteCorrectDataToResponse(documentData, response);

            response.End();
            response.Flush();
        } 

        public static void LoadFile(string fileName, object documentData)
        {
            LoadFile(fileName, GetFileContentType(fileName), documentData);
        }

        public static string GetFileContentType(string documentName)
        {
            switch (GetExtension(documentName))
            {
                case FILE_TYPE_DOC:
                    return CONTENT_TYPE_DOC;
                case FILE_TYPE_TXT:
                    return CONTENT_TYPE_TXT;
                case FILE_TYPE_PDF:
                    return CONTENT_TYPE_PDF;
                default:
                    return CONTENT_TYPE_OCTETSTREAM;
            }
        }

        public static string GetExtension(string documentName)
        {
            return Regex.Replace(new FileInfo(documentName).Extension, "^\\.", "").ToLower();
        }

        #endregion


        #region Private Methods

        private static void AddAttachmentHeader(string fileName)
        {
            HttpContext.Current.Response.AddHeader("Content-Disposition", "attachment; filename=" + FormatFileNameForStreaming(fileName));
        }

        private static void WriteCorrectDataToResponse(object documentData, HttpResponse response)
        {
            if (documentData is byte[])
            {
                var binaryData = (byte[])documentData;
                response.AddHeader("Content-length", binaryData.Length.ToString());
                response.AddHeader("Accept-Header", binaryData.Length.ToString());
                response.AddHeader("Accept-Ranges", "bytes");
                response.BinaryWrite(binaryData);
            }
        }

        private static string FormatFileNameForStreaming(string fileName)
        {
            return fileName.Replace(" ", "%20");
        }

        #endregion
    }
}
